package cc.higou.core.controller;

import cc.higou.core.pojo.Cart;
import cc.higou.core.pojo.Item;
import cc.higou.core.tools.SessionTool;
import cc.higou.service.CartService;
import cc.higou.service.SessionService;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;

/**
 * 说明：
 * 购物车的控制器
 *
 * @author:dongxing
 * @time:--
 */
@Controller
public class CartController {

    @Autowired
    private CartService cartService;
    @Autowired
    private SessionService sessionService;

    /**
     * 未登录的情况下，将购物车的信息展示给用户
     *
     * @param request
     * @param model
     * @return
     */
    @RequestMapping(value = "/cart")
    public String showCart(HttpServletRequest request, HttpServletResponse response, Model model) {

        try {
            //cookie中的cart
            Cart cart1 = null;
            //redis中的cart
            Cart cart2 = null;
            //合并后的cart
            Cart cart = null;

            //将cookie中的查询的cart对象给前台
            cart1 = this.getCartFromCookie(request);

            //判断用户有没有登录
            String xingsessid = SessionTool.getSession(request, response);
            String username = sessionService.getUserFromRedis(xingsessid);
            //如果登录了，从redis中获取相关的信息
            if (username != null) {
                cart2 = cartService.getCartFromRedis(username);
            }
            //合并后的购物车
            cart = this.mergeCart(cart1, cart2);


            //登录的情况下将合并后的购物车信息存放到jedis中
            if (username != null) {
                //删除cookie中的数据
                this.delCartFormCookies(response);
                //将数据添加到redis中
                cartService.addCartToRedis(username, cart);
            }

            //自我填充cart对象中的item的sku
            cart = cartService.fillItemsSkus(cart);

            model.addAttribute("cart", cart);


        } catch (IOException e) {
            e.printStackTrace();
        }
        return "cart";
    }

    /**
     * 添加购物车
     *
     * @param request
     * @param response
     * @param skuId
     * @param amount
     * @return
     */
    @RequestMapping(value = "/addCart")
    public String addCart(HttpServletRequest request, HttpServletResponse response, Long skuId, Integer amount) {

        try {

            Cart cart = null;

            //判断用户是否登陆
            String xingsessid = SessionTool.getSession(request, response);
            String username = sessionService.getUserFromRedis(xingsessid);
            //表示用户登录了
            // 用户登录从redis中取出购物车
            if (username != null) {
                cart = cartService.getCartFromRedis(username);

            } else {
                //获得用户的cookie中的数据
                cart = this.getCartFromCookie(request);
            }
            // 如果未登录的cookie，以及已登录的redis都没有购物车，则新建一个
            if (cart == null) {
                cart = new Cart();
            }

            // 将新item添加到新cart中
            Item item = new Item();
            item.setSkuId(skuId);
            item.setAmount(amount);
            //将页面的购物信息存放到cart对象中
            cart.addItem(item);

            //用户登录
            if (username != null) {
                // 将购物车保存到redis
                cartService.addCartToRedis(username, cart);
            } else {
                // 用户没有登录
                //将新cart反存到cookie中
                this.setCartToCookie(cart, response);
            }


        } catch (IOException e) {
            e.printStackTrace();
        }
        return "redirect:/cart";
    }

    /**
     * 结算 skuIds表示用户从购物车中选择的商品
     *
     * @param ids
     * @param model
     * @param request
     * @param response
     * @return
     */

    @RequestMapping(value = "/buyer/trueBuy")
    public String trueBuy(Long[] ids, Model model, HttpServletRequest request, HttpServletResponse response) {

        String xingsessid = SessionTool.getSession(request, response);
        String username = sessionService.getUserFromRedis(xingsessid);

        //无货标识(true表示有货)
        Boolean flag = true;

        // 判断redis里的购物车不能为空，也不能是空车子
        try {
            Cart cart = cartService.getCartFromRedis(username);
            if (cart != null && cart.getItems().size() > 0) {
                // 填充购物车 复合信息（具体库存相关信息）
                cart = cartService.fillItemsSkus(cart);
                List<Item> items = cart.getItems();
                for (Item item : items) {
                    // 购买数量大于库存数量
                    if (item.getAmount() > Integer.parseInt(item.getSku().get("stock") + "")) {
                        item.setHave(false);
                        flag = false;
                    }
                }
                //至少有一款商品无货
                if (!flag) {
                    model.addAttribute("cart", cart);
                    return "/cart";
                }
            } else {
                // 回到空的购物车页面
                return "redirect:/cart";

            }
            // 最后有货进入订单页面
            return "order";


        } catch (IOException e) {
            e.printStackTrace();
        }
        return "redirect:http://localhost:8083/";
    }

    /**
     * 自定义一个方法实行从cookie中查询已经存在的购物车信息
     *
     * @param request
     * @return
     * @throws IOException
     */
    private Cart getCartFromCookie(HttpServletRequest request) throws IOException {
        Cookie[] cookies = request.getCookies();
        if (cookies != null) {
            for (Cookie cookie : cookies) {
                if (cookie.getName().equals("cart")) {
                    ObjectMapper mapper = new ObjectMapper();
                    String value = cookie.getValue();
                    Cart cart = mapper.readValue(value, Cart.class);
                    return cart;
                }
            }
        }
        return null;

    }


    /**
     * 将新cart反存到cookie中
     *
     * @param cart
     * @param response
     */
    private void setCartToCookie(Cart cart, HttpServletResponse response) throws JsonProcessingException {
        //将cart对象变成json字符串
        ObjectMapper mapper = new ObjectMapper();
        //忽略null
        mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);

        String s = mapper.writeValueAsString(cart);
        //创建新的cookie
        Cookie cookie = new Cookie("cart", s);
        //设置cookie的存活时间
        cookie.setMaxAge(60 * 60 * 24 * 7);

        //设置路径
        cookie.setPath("/");

        response.addCookie(cookie);

    }

    /**
     * 合并两处购物车对象
     *
     * @param cart1 cookie中的购物车
     * @param cart2 redis中的购物车
     * @return
     */
    private Cart mergeCart(Cart cart1, Cart cart2) {
        if (cart1 == null) {
            return cart2;
        } else if (cart2 == null) {
            return cart1;
        } else {
            // 则合并购物车
            List<Item> items = cart2.getItems();
            for (Item item : items) {
                cart1.addItem(item);
            }
            return cart1;
        }

    }

    /**
     * 将购物车从cookie中删除
     *
     * @param response
     */

    private void delCartFormCookies(HttpServletResponse response) {
        //将cookie中的值删除
        Cookie cookie = new Cookie("cart", "");
        cookie.setMaxAge(0);
        cookie.setPath("/");
        response.addCookie(cookie);

    }

}
